<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Zookeeper Leader 选举机制深度解析</title>
    <link href="https://cdn.staticfile.org/font-awesome/6.4.0/css/all.min.css" rel="stylesheet">
    <link href="https://cdn.staticfile.org/tailwindcss/2.2.19/tailwind.min.css" rel="stylesheet">
    <link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;500;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
    <script src="https://cdn.jsdelivr.net/npm/mermaid@latest/dist/mermaid.min.js"></script>
    <style>
        body {
            font-family: 'Noto Sans SC', Tahoma, Arial, Roboto, "Droid Sans", "Helvetica Neue", "Droid Sans Fallback", "Heiti SC", "Hiragino Sans GB", Simsun, sans-serif;
            background: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
            min-height: 100vh;
        }
        
        .hero-gradient {
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
        }
        
        .content-card {
            background: rgba(255, 255, 255, 0.95);
            backdrop-filter: blur(10px);
            box-shadow: 0 20px 40px rgba(0, 0, 0, 0.1);
            transition: transform 0.3s ease, box-shadow 0.3s ease;
        }
        
        .content-card:hover {
            transform: translateY(-5px);
            box-shadow: 0 25px 50px rgba(0, 0, 0, 0.15);
        }
        
        .section-title {
            position: relative;
            padding-left: 20px;
        }
        
        .section-title::before {
            content: '';
            position: absolute;
            left: 0;
            top: 50%;
            transform: translateY(-50%);
            width: 4px;
            height: 24px;
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            border-radius: 2px;
        }
        
        .highlight-box {
            background: linear-gradient(135deg, #f093fb 0%, #f5576c 100%);
            color: white;
            padding: 20px;
            border-radius: 12px;
            margin: 20px 0;
            position: relative;
            overflow: hidden;
        }
        
        .highlight-box::before {
            content: '';
            position: absolute;
            top: -50%;
            right: -50%;
            width: 200%;
            height: 200%;
            background: radial-gradient(circle, rgba(255,255,255,0.1) 0%, transparent 70%);
            animation: shimmer 3s infinite;
        }
        
        @keyframes shimmer {
            0% { transform: rotate(0deg); }
            100% { transform: rotate(360deg); }
        }
        
        .process-step {
            position: relative;
            padding-left: 40px;
            margin-bottom: 30px;
        }
        
        .process-step::before {
            content: attr(data-step);
            position: absolute;
            left: 0;
            top: 0;
            width: 30px;
            height: 30px;
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            color: white;
            border-radius: 50%;
            display: flex;
            align-items: center;
            justify-content: center;
            font-weight: bold;
            font-size: 14px;
        }
        
        .mermaid {
            background: white;
            padding: 20px;
            border-radius: 12px;
            box-shadow: 0 10px 30px rgba(0, 0, 0, 0.1);
        }
        
        .feature-icon {
            width: 60px;
            height: 60px;
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            border-radius: 50%;
            display: flex;
            align-items: center;
            justify-content: center;
            color: white;
            font-size: 24px;
            margin-bottom: 15px;
        }
        
        .code-highlight {
            background: #f3f4f6;
            padding: 2px 8px;
            border-radius: 4px;
            font-family: 'Courier New', monospace;
            color: #6366f1;
            font-size: 14px;
        }
    </style>
</head>
<body>
    <!-- Hero Section -->
    <div class="hero-gradient text-white py-20">
        <div class="container mx-auto px-6">
            <div class="max-w-4xl mx-auto text-center">
                <h1 class="text-5xl md:text-6xl font-bold mb-6 animate-pulse">
                    <i class="fas fa-network-wired mr-4"></i>
                    Zookeeper Leader 选举机制
                </h1>
                <p class="text-xl md:text-2xl opacity-90 leading-relaxed">
                    深入解析分布式系统中的核心共识算法
                </p>
                <div class="mt-8 flex justify-center space-x-6">
                    <div class="text-center">
                        <i class="fas fa-shield-alt text-3xl mb-2"></i>
                        <p class="text-sm">高可用性</p>
                    </div>
                    <div class="text-center">
                        <i class="fas fa-sync-alt text-3xl mb-2"></i>
                        <p class="text-sm">一致性保障</p>
                    </div>
                    <div class="text-center">
                        <i class="fas fa-bolt text-3xl mb-2"></i>
                        <p class="text-sm">快速恢复</p>
                    </div>
                </div>
            </div>
        </div>
    </div>

    <!-- Main Content -->
    <div class="container mx-auto px-6 py-12">
        <!-- Introduction Card -->
        <div class="content-card rounded-2xl p-8 mb-8">
            <p class="text-lg leading-relaxed text-gray-700 indent-8">
                Zookeeper 的 Leader 选举是其高可用性和一致性保障的关键部分。Leader 选举是为了确保在 Zookeeper 集群中的一个节点（Leader）能够处理所有写操作，其他节点（Follower）则处理读操作，从而保持数据一致性。
            </p>
        </div>

        <!-- Election Process Overview -->
        <div class="content-card rounded-2xl p-8 mb-8">
            <h2 class="section-title text-3xl font-bold text-gray-800 mb-6">
                <i class="fas fa-vote-yea mr-3 text-purple-600"></i>
                选举过程概述
            </h2>
            <p class="text-gray-700 mb-6 indent-8">
                Zookeeper 集群由多个节点组成，每个节点都有可能成为 Leader。在集群启动时或 Leader 节点失效时，Zookeeper 需要进行 Leader 选举。选举的过程包括以下步骤：
            </p>
            
            <div class="grid md:grid-cols-3 gap-6">
                <div class="process-step" data-step="1">
                    <h4 class="font-bold text-lg mb-2">初始化</h4>
                    <p class="text-gray-600">每个节点在启动时会发送一个选举请求，声明自己有意成为 Leader。</p>
                </div>
                <div class="process-step" data-step="2">
                    <h4 class="font-bold text-lg mb-2">选举算法</h4>
                    <p class="text-gray-600">Zookeeper 使用 ZAB（Zookeeper Atomic Broadcast）协议中的 Leader 选举算法，确保选举的可靠性和一致性。</p>
                </div>
                <div class="process-step" data-step="3">
                    <h4 class="font-bold text-lg mb-2">选举结果</h4>
                    <p class="text-gray-600">最终会选出一个 Leader，其他节点成为 Follower。Leader 节点会接管所有写操作并协调事务的提交。</p>
                </div>
            </div>
        </div>

        <!-- ZAB Protocol Visualization -->
        <div class="content-card rounded-2xl p-8 mb-8">
            <h2 class="section-title text-3xl font-bold text-gray-800 mb-6">
                <i class="fas fa-project-diagram mr-3 text-purple-600"></i>
                ZAB 协议选举流程
            </h2>
            <div class="mermaid">
                graph TD
                    A[节点启动] --> B[生成 zxid 和节点 ID]
                    B --> C[广播选举请求]
                    C --> D{接收其他节点请求}
                    D --> E[比较 zxid]
                    E --> F{zxid 相同?}
                    F -->|是| G[比较节点 ID]
                    F -->|否| H[选择最高 zxid]
                    G --> I[投票给节点 ID 较小者]
                    H --> I
                    I --> J{获得多数票?}
                    J -->|是| K[成为 Leader]
                    J -->|否| L[成为 Follower]
                    K --> M[数据同步]
                    L --> M
                    M --> N[集群正常运行]
            </div>
        </div>

        <!-- Algorithm Details -->
        <div class="content-card rounded-2xl p-8 mb-8">
            <h2 class="section-title text-3xl font-bold text-gray-800 mb-6">
                <i class="fas fa-cogs mr-3 text-purple-600"></i>
                Leader 选举的算法
            </h2>
            <p class="text-gray-700 mb-6 indent-8">
                Zookeeper 的 Leader 选举算法是基于 <strong>ZAB 协议</strong>（Zookeeper Atomic Broadcast），其算法过程如下：
            </p>

            <!-- Algorithm Steps -->
            <div class="space-y-6">
                <div class="bg-gradient-to-r from-purple-50 to-pink-50 p-6 rounded-xl">
                    <h3 class="text-xl font-bold mb-4 flex items-center">
                        <i class="fas fa-play-circle mr-3 text-purple-600"></i>
                        启动选举
                    </h3>
                    <ul class="space-y-3">
                        <li class="flex items-start">
                            <i class="fas fa-broadcast-tower mt-1 mr-3 text-purple-500"></i>
                            <div>
                                <strong>广播选举请求</strong>：每个节点启动时会发送一个选举请求到集群中的所有其他节点，声明自己希望成为 Leader。
                            </div>
                        </li>
                        <li class="flex items-start">
                            <i class="fas fa-inbox mt-1 mr-3 text-purple-500"></i>
                            <div>
                                <strong>接收请求</strong>：其他节点接收到选举请求后，会记录下请求的候选者信息，并回复选举结果。
                            </div>
                        </li>
                    </ul>
                </div>

                <div class="bg-gradient-to-r from-blue-50 to-indigo-50 p-6 rounded-xl">
                    <h3 class="text-xl font-bold mb-4 flex items-center">
                        <i class="fas fa-tasks mr-3 text-blue-600"></i>
                        选举过程
                    </h3>
                    
                    <div class="space-y-4">
                        <div>
                            <h4 class="font-bold mb-2">1. 初始化阶段</h4>
                            <p class="text-gray-700 pl-4">
                                每个节点在启动时会生成一个唯一的 <span class="code-highlight">zxid</span>（Zookeeper Transaction ID），用来标识节点的事务状态。
                                节点会根据 <span class="code-highlight">zxid</span> 和 <span class="code-highlight">节点ID</span> 来发起选举请求。
                            </p>
                        </div>
                        
                        <div>
                            <h4 class="font-bold mb-2">2. 选举请求和投票</h4>
                            <p class="text-gray-700 pl-4">
                                节点将自己的 <span class="code-highlight">zxid</span> 和 <span class="code-highlight">节点ID</span> 发送给集群中的其他节点。
                                每个节点在接收到选举请求后，比较请求中的 <span class="code-highlight">zxid</span> 和自己节点的 <span class="code-highlight">zxid</span>，并根据规则进行投票。
                            </p>
                        </div>
                        
                        <div>
                            <h4 class="font-bold mb-2">3. 选举规则</h4>
                            <div class="highlight-box">
                                <p class="font-bold mb-2">
                                    <i class="fas fa-crown mr-2"></i>
                                    最高 <span class="code-highlight text-white bg-white bg-opacity-30 px-2 py-1 rounded">zxid</span> 优先
                                </p>
                                <p>节点会选择具有最高 <span class="code-highlight text-white bg-white bg-opacity-30 px-2 py-1 rounded">zxid</span> 的候选者作为 Leader。
                                如果多个候选者的 <span class="code-highlight text-white bg-white bg-opacity-30 px-2 py-1 rounded">zxid</span> 相同，则比较节点 ID，节点 ID 较小的优先。</p>
                            </div>
                        </div>
                        
                        <div>
                            <h4 class="font-bold mb-2">4